package constructor;

/**
 * Java构造函数使用详解
 * 
 * 构造函数是Java中用于初始化对象的特殊方法。
 * 它在创建对象时自动调用，确保对象在使用前被正确初始化。
 */
public class ConstructorDemo {
    private String name;
    private int age;
    private String email;
    
    // 1. 默认构造函数（无参构造函数）
    public ConstructorDemo() {
        this.name = "Unknown";
        this.age = 0;
        this.email = "unknown@example.com";
        System.out.println("调用了默认构造函数");
    }
    
    // 2. 带参数的构造函数
    public ConstructorDemo(String name, int age) {
        this.name = name;
        this.age = age;
        this.email = "unknown@example.com";
        System.out.println("调用了带参数的构造函数(name, age)");
    }
    
    // 3. 完整参数的构造函数
    public ConstructorDemo(String name, int age, String email) {
        this.name = name;
        this.age = age;
        this.email = email;
        System.out.println("调用了完整参数的构造函数(name, age, email)");
    }
    
    // 4. 私有构造函数 - 用于单例模式等场景
    private ConstructorDemo(String name) {
        this.name = name;
        this.age = 0;
        this.email = "private@example.com";
        System.out.println("调用了私有构造函数");
    }
    
    // 静态方法创建实例 - 配合私有构造函数使用
    public static ConstructorDemo createInstance(String name) {
        return new ConstructorDemo(name);
    }
    
    // 拷贝构造函数 - 创建一个与现有对象相同的实例
    public ConstructorDemo(ConstructorDemo other) {
        this.name = other.name;
        this.age = other.age;
        this.email = other.email;
        System.out.println("调用了拷贝构造函数");
    }
    
    // Getter方法
    public String getName() {
        return name;
    }
    
    public int getAge() {
        return age;
    }
    
    public String getEmail() {
        return email;
    }
    
    // toString方法用于输出对象信息
    @Override
    public String toString() {
        return "ConstructorDemo{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", email='" + email + '\'' +
                '}';
    }
    
    // 主方法用于演示构造函数的使用
    public static void main(String[] args) {
        System.out.println("=== Java构造函数使用示例 ===\n");
        
        // 使用默认构造函数
        System.out.println("1. 使用默认构造函数:");
        ConstructorDemo person1 = new ConstructorDemo();
        System.out.println("对象信息: " + person1);
        System.out.println();
        
        // 使用带参数的构造函数
        System.out.println("2. 使用带参数的构造函数:");
        ConstructorDemo person2 = new ConstructorDemo("张三", 25);
        System.out.println("对象信息: " + person2);
        System.out.println();
        
        // 使用完整参数的构造函数
        System.out.println("3. 使用完整参数的构造函数:");
        ConstructorDemo person3 = new ConstructorDemo("李四", 30, "lisi@example.com");
        System.out.println("对象信息: " + person3);
        System.out.println();
        
        // 使用静态方法创建实例（配合私有构造函数）
        System.out.println("4. 使用静态方法创建实例:");
        ConstructorDemo person4 = ConstructorDemo.createInstance("王五");
        System.out.println("对象信息: " + person4);
        System.out.println();
        
        // 使用拷贝构造函数
        System.out.println("5. 使用拷贝构造函数:");
        ConstructorDemo person5 = new ConstructorDemo(person2);
        System.out.println("对象信息: " + person5);
        System.out.println();
        
        // 演示构造函数链 - 通过this()调用其他构造函数
        System.out.println("=== 构造函数链示例 ===");
        ConstructorDemoWithChaining demo1 = new ConstructorDemoWithChaining();
        System.out.println("对象信息: " + demo1);
        
        ConstructorDemoWithChaining demo2 = new ConstructorDemoWithChaining("赵六");
        System.out.println("对象信息: " + demo2);
        
        ConstructorDemoWithChaining demo3 = new ConstructorDemoWithChaining("孙七", 28);
        System.out.println("对象信息: " + demo3);
        
        ConstructorDemoWithChaining demo4 = new ConstructorDemoWithChaining("周八", 35, "zhouba@example.com");
        System.out.println("对象信息: " + demo4);
    }
}

/**
 * 演示构造函数链的类
 * 使用this()关键字调用其他构造函数
 */
class ConstructorDemoWithChaining {
    private String name;
    private int age;
    private String email;
    
    // 默认构造函数调用参数最多的构造函数
    public ConstructorDemoWithChaining() {
        this("默认姓名", 0, "default@example.com");
        System.out.println("执行了默认构造函数");
    }
    
    // 调用三个参数的构造函数
    public ConstructorDemoWithChaining(String name) {
        this(name, 0, "unknown@example.com");
        System.out.println("执行了单参数构造函数");
    }
    
    // 调用三个参数的构造函数
    public ConstructorDemoWithChaining(String name, int age) {
        this(name, age, "unknown@example.com");
        System.out.println("执行了双参数构造函数");
    }
    
    // 主构造函数
    public ConstructorDemoWithChaining(String name, int age, String email) {
        this.name = name;
        this.age = age;
        this.email = email;
        System.out.println("执行了三参数构造函数");
    }
    
    @Override
    public String toString() {
        return "ConstructorDemoWithChaining{" +
                "name='" + name + '\'' +
                ", age=" + age +
                ", email='" + email + '\'' +
                '}';
    }
}